{% extends "base.html" %}

{% block title %}选择PPT模板{% endblock %}

{% block extra_css %}
<style>
/* 现代化模板选择页面 */
.template-selection-hero {
    background: var(--glass-bg);
    backdrop-filter: blur(30px);
    border: 1px solid var(--glass-border);
    color: var(--text-primary);
    padding: var(--spacing-2xl) var(--spacing-lg);
    margin: calc(-1 * var(--spacing-lg)) calc(-1 * var(--spacing-lg)) var(--spacing-2xl) calc(-1 * var(--spacing-lg));
    text-align: center;
    position: relative;
    overflow: hidden;
    border-radius: 0 0 var(--border-radius-xl) var(--border-radius-xl);
}

.template-selection-hero::before {
    content: '';
    position: absolute;
    top: 0;
    left: 0;
    right: 0;
    bottom: 0;
    background:
        radial-gradient(circle at 30% 30%, rgba(67, 233, 123, 0.1) 0%, transparent 50%),
        radial-gradient(circle at 70% 70%, rgba(240, 147, 251, 0.1) 0%, transparent 50%);
    animation: templateSelectionFloat 18s ease-in-out infinite;
}

@keyframes templateSelectionFloat {
    0%, 100% { transform: scale(1) rotate(0deg); }
    50% { transform: scale(1.03) rotate(-1deg); }
}

.template-selection-hero h1 {
    font-size: 2.2rem;
    font-weight: 700;
    margin-bottom: var(--spacing-md);
    background: var(--primary-gradient);
    -webkit-background-clip: text;
    -webkit-text-fill-color: transparent;
    background-clip: text;
    position: relative;
    z-index: 1;
    letter-spacing: -0.02em;
}

.template-selection-hero p {
    font-size: 1.5rem;
    color: var(--text-secondary);
    margin: 0;
    position: relative;
    z-index: 1;
    font-weight: 500;
}

.project-info {
    display: inline-block;
    background: var(--glass-bg);
    backdrop-filter: blur(15px);
    border: 1px solid var(--glass-border);
    padding: var(--spacing-md) var(--spacing-lg);
    border-radius: var(--border-radius-lg);
    box-shadow: 0 4px 20px rgba(67, 233, 123, 0.2);
    position: relative;
    z-index: 1;
}

.project-info strong {
    color: var(--text-primary);
    font-weight: 600;
}
</style>
{% endblock %}

{% block content %}
<div class="template-selection-hero">
    <h1>选择PPT模板</h1>
    <p>为您的PPT选择一个合适的模板模板</p>
    <div class="project-info">
        <strong>项目：</strong><span id="projectTopic">{{ project_topic or '未知项目' }}</span>
    </div>
</div>

<div style="max-width: 1400px; margin: 0 auto; padding: var(--spacing-lg);">

    <!-- Search and Filter Controls -->
    <div class="search-filter-controls" style="background: var(--glass-bg); backdrop-filter: blur(15px); border: 1px solid var(--glass-border); border-radius: var(--border-radius-lg); box-shadow: var(--glass-shadow); padding: var(--spacing-xl); margin-bottom: var(--spacing-xl);">
        <div style="display: flex; flex-wrap: wrap; gap: var(--spacing-lg); align-items: center; justify-content: space-between;">
            <!-- Search Box -->
            <div style="flex: 1; min-width: 300px;">
                <div style="position: relative;">
                    <input
                        type="text"
                        id="searchInput"
                        placeholder="搜索模板名称或描述..."
                        style="width: 100%; padding: var(--spacing-md) var(--spacing-lg) var(--spacing-md) 50px; border: 1px solid var(--glass-border); border-radius: var(--border-radius-md); background: rgba(255, 255, 255, 0.1); backdrop-filter: blur(10px); color: var(--text-primary); font-size: 1rem; transition: all 0.3s ease;"
                        onkeypress="if(event.key==='Enter') performSearch()"
                    >
                    <div style="position: absolute; left: var(--spacing-md); top: 50%; transform: translateY(-50%); color: var(--text-muted); font-size: 1.2rem;">🔍</div>
                    <button
                        id="clearSearchBtn"
                        onclick="clearSearch()"
                        style="position: absolute; right: var(--spacing-md); top: 50%; transform: translateY(-50%); background: none; border: none; color: var(--text-muted); cursor: pointer; font-size: 1.2rem; display: none;"
                        title="清除搜索"
                    >✕</button>
                </div>
            </div>

            <!-- Tag Filter -->
            <div style="display: flex; align-items: center; gap: var(--spacing-md);">
                <label style="color: var(--text-secondary); font-weight: 600; white-space: nowrap;">分类筛选:</label>
                <select
                    id="tagFilter"
                    onchange="filterByTag()"
                    style="padding: var(--spacing-md) var(--spacing-lg); border: 1px solid var(--glass-border); border-radius: var(--border-radius-md); background: rgba(255, 255, 255, 0.1); backdrop-filter: blur(10px); color: var(--text-primary); font-size: 0.9rem; min-width: 120px;"
                >
                    <option value="">全部分类</option>
                    <!-- Options will be populated dynamically -->
                </select>
            </div>

            <!-- Search Button -->
            <button
                onclick="performSearch()"
                class="btn btn-primary"
                style="padding: var(--spacing-md) var(--spacing-xl); white-space: nowrap;"
            >
                搜索
            </button>
        </div>

        <!-- Active Filters Display -->
        <div id="activeFilters" style="margin-top: var(--spacing-md); display: none;">
            <div style="display: flex; flex-wrap: wrap; gap: var(--spacing-sm); align-items: center;">
                <span style="color: var(--text-secondary); font-size: 0.9rem; font-weight: 600;">当前筛选:</span>
                <div id="filterTags" style="display: flex; flex-wrap: wrap; gap: var(--spacing-sm);"></div>
                <button onclick="clearAllFilters()" style="background: none; border: none; color: var(--text-muted); cursor: pointer; font-size: 0.8rem; text-decoration: underline;">清除所有</button>
            </div>
        </div>
    </div>

    <!-- Template Selection Grid -->
    <div id="templatesGrid" style="display: grid; grid-template-columns: repeat(auto-fill, minmax(380px, 1fr)); gap: var(--spacing-xl);">
        <!-- Templates will be loaded here -->
    </div>

    <!-- Loading indicator -->
    <div id="loadingIndicator" style="text-align: center; padding: var(--spacing-2xl); display: none;">
        <div style="display: inline-block; width: 50px; height: 50px; border: 4px solid rgba(67, 233, 123, 0.2); border-top: 4px solid var(--success-gradient); border-radius: 50%; animation: spin 1s linear infinite;"></div>
        <p style="margin-top: var(--spacing-lg); color: var(--text-secondary); font-weight: 600; font-size: 1.1rem;">🎨 正在加载精美模板...</p>
        <p style="margin-top: var(--spacing-sm); color: var(--text-muted); font-size: 0.9rem;">请稍候，为您准备最佳的模板选择</p>
    </div>

    <!-- Pagination Controls -->
    <div id="paginationContainer" style="display: none; margin-top: var(--spacing-xl); text-align: center;">
        <div style="background: var(--glass-bg); backdrop-filter: blur(15px); border: 1px solid var(--glass-border); border-radius: var(--border-radius-lg); box-shadow: var(--glass-shadow); padding: var(--spacing-lg); display: inline-block;">
            <div style="display: flex; align-items: center; gap: var(--spacing-md); flex-wrap: wrap; justify-content: center;">
                <!-- Previous Button -->
                <button id="prevPageBtn" onclick="changePage(currentPage - 1)" class="btn btn-secondary btn-sm" disabled>
                    ← 上一页
                </button>

                <!-- Page Numbers -->
                <div id="pageNumbers" style="display: flex; gap: var(--spacing-xs); align-items: center; flex-wrap: wrap;">
                    <!-- Page numbers will be generated here -->
                </div>

                <!-- Next Button -->
                <button id="nextPageBtn" onclick="changePage(currentPage + 1)" class="btn btn-secondary btn-sm" disabled>
                    下一页 →
                </button>
            </div>

            <!-- Page Info -->
            <div id="pageInfo" style="margin-top: var(--spacing-md); color: var(--text-secondary); font-size: 0.9rem;">
                <!-- Page info will be displayed here -->
            </div>
        </div>
    </div>

    <!-- Action Buttons -->
    <div style="text-align: center; margin-top: var(--spacing-2xl); padding: var(--spacing-xl); background: var(--glass-bg); backdrop-filter: blur(15px); border: 1px solid var(--glass-border); border-radius: var(--border-radius-lg); box-shadow: var(--glass-shadow);">
        <div style="margin-bottom: var(--spacing-lg);">
            <span style="color: var(--text-secondary); font-size: 1.1rem; font-weight: 500;">选择模板后点击下方按钮开始生成PPT</span>
        </div>
        <div style="display: flex; gap: var(--spacing-lg); justify-content: center; flex-wrap: wrap;">
            <button id="startGenerationBtn" class="btn btn-primary" disabled style="padding: var(--spacing-lg) var(--spacing-2xl); font-size: 1.1rem;">
                🚀 开始生成PPT
            </button>
            <button id="skipSelectionBtn" class="btn btn-secondary" style="padding: var(--spacing-lg) var(--spacing-2xl); font-size: 1.1rem;">
                ⏭️ 使用默认模板
            </button>
        </div>
    </div>

    <!-- Selected Template Info -->
    <div id="selectedTemplateInfo" style="display: none; margin-top: var(--spacing-xl); padding: var(--spacing-xl); background: rgba(67, 233, 123, 0.1); backdrop-filter: blur(10px); border-radius: var(--border-radius-lg); border-left: 4px solid var(--success-gradient); box-shadow: 0 4px 20px rgba(67, 233, 123, 0.2);">
        <h4 style="margin: 0 0 var(--spacing-md) 0; color: var(--text-primary); font-weight: 600;">✅ 已选择模板</h4>
        <div id="selectedTemplateDetails" style="color: var(--text-secondary);"></div>
    </div>
</div>

<!-- Template Preview Modal -->
<div id="previewModal" class="modal" style="display: none;">
    <div class="modal-content" style="max-width: 95%; width: 95%; max-height: 95vh;">
        <div class="modal-header">
            <h2 id="previewTitle">模板预览</h2>
            <span class="close" id="closePreviewModal">&times;</span>
        </div>
        <div class="modal-body" style="text-align: center;">
            <iframe id="previewFrame" style="width: 1280px; height: 720px; border: 1px solid #ddd; transform: scale(0.8); transform-origin: top left; margin: 0 auto;"></iframe>
        </div>
    </div>
</div>

<style>
@keyframes spin {
    0% { transform: rotate(0deg); }
    100% { transform: rotate(360deg); }
}

.modal {
    position: fixed;
    z-index: 1000;
    left: 0;
    top: 0;
    width: 100%;
    height: 100%;
    background-color: rgba(0,0,0,0.5);
    display: flex;
    justify-content: center;
    align-items: center;
}

.modal-content {
    background-color: white;
    border-radius: 8px;
    box-shadow: 0 4px 6px rgba(0,0,0,0.1);
}

.modal-header {
    display: flex;
    justify-content: space-between;
    align-items: center;
    padding: 20px;
    border-bottom: 1px solid #eee;
}

.modal-header h2 {
    margin: 0;
    color: #2c3e50;
}

.close {
    font-size: 28px;
    font-weight: bold;
    cursor: pointer;
    color: #aaa;
}

.close:hover {
    color: #000;
}

.modal-body {
    padding: 20px;
}

.template-card {
    background: var(--glass-bg);
    backdrop-filter: blur(20px);
    border: 1px solid var(--glass-border);
    border-radius: var(--border-radius-lg);
    box-shadow: var(--glass-shadow);
    overflow: hidden;
    transition: all 0.4s cubic-bezier(0.4, 0, 0.2, 1);
    display: flex;
    flex-direction: column;
    height: auto;
    position: relative;
    cursor: pointer;
}

.template-card::before {
    content: '';
    position: absolute;
    top: 0;
    left: 0;
    right: 0;
    height: 3px;
    background: var(--warning-gradient);
    transform: scaleX(0);
    transition: transform 0.4s ease;
}

.template-card:hover {
    transform: translateY(-8px) scale(1.02);
    box-shadow: 0 20px 60px rgba(31, 38, 135, 0.3);
}

.template-card:hover::before {
    transform: scaleX(1);
}

.template-card.selected {
    border-color: rgba(67, 233, 123, 0.5);
    box-shadow: 0 20px 60px rgba(67, 233, 123, 0.3);
    transform: translateY(-8px) scale(1.02);
}

.template-card.selected::before {
    transform: scaleX(1);
    background: var(--success-gradient);
}

.template-preview {
    width: 100%;
    height: 225px;
    background: #f8f9fa;
    position: relative;
    border-bottom: 1px solid #eee;
    overflow: hidden;
    border-radius: 12px 12px 0 0;
    flex-shrink: 0;
}

.template-preview img {
    max-width: 100%;
    max-height: 100%;
    object-fit: contain;
}

.template-info {
    padding: 18px;
    flex-grow: 1;
    display: flex;
    flex-direction: column;
    justify-content: space-between;
}



.tag {
    display: inline-block;
    background: rgba(102, 126, 234, 0.1);
    color: #667eea;
    padding: 4px 12px;
    border-radius: var(--border-radius-sm);
    font-size: 0.75rem;
    font-weight: 500;
    margin-right: 6px;
    margin-bottom: 6px;
    border: 1px solid rgba(102, 126, 234, 0.2);
    backdrop-filter: blur(10px);
    transition: all 0.3s ease;
}

.tag:hover {
    background: rgba(102, 126, 234, 0.15);
    transform: translateY(-1px);
}

.default-badge {
    background: var(--success-gradient);
    color: white;
    padding: 4px 12px;
    border-radius: var(--border-radius-sm);
    font-size: 0.7rem;
    font-weight: 600;
    box-shadow: 0 2px 8px rgba(67, 233, 123, 0.3);
    border: 1px solid rgba(255, 255, 255, 0.2);
    backdrop-filter: blur(10px);
}



.template-actions {
    padding: 16px 20px;
    border-top: 1px solid rgba(255, 255, 255, 0.1);
    background: rgba(255, 255, 255, 0.05);
    display: flex;
    gap: 8px;
    justify-content: flex-end;
    flex-wrap: wrap;
    backdrop-filter: blur(10px);
}

.btn {
    padding: 12px 24px;
    border: none;
    border-radius: var(--border-radius-md);
    cursor: pointer;
    font-size: 0.9rem;
    font-weight: 600;
    text-decoration: none;
    display: inline-flex;
    align-items: center;
    justify-content: center;
    gap: 8px;
    text-align: center;
    transition: all 0.3s cubic-bezier(0.4, 0, 0.2, 1);
    position: relative;
    overflow: hidden;
    backdrop-filter: blur(10px);
    border: 1px solid rgba(255, 255, 255, 0.2);
    box-shadow: 0 4px 15px rgba(0, 0, 0, 0.1);
    white-space: nowrap;
}

.btn::before {
    content: '';
    position: absolute;
    top: 0;
    left: -100%;
    width: 100%;
    height: 100%;
    background: linear-gradient(90deg, transparent, rgba(255,255,255,0.2), transparent);
    transition: left 0.5s;
}

.btn:hover::before {
    left: 100%;
}

.btn:hover {
    transform: translateY(-2px);
    box-shadow: 0 8px 25px rgba(0, 0, 0, 0.15);
}

.btn:active {
    transform: translateY(0);
}

.btn-primary {
    background: var(--primary-gradient);
    color: white;
    box-shadow: 0 4px 15px rgba(102, 126, 234, 0.3);
}
.btn-primary:hover {
    box-shadow: 0 8px 25px rgba(102, 126, 234, 0.4);
    transform: translateY(-2px) scale(1.02);
}
.btn-primary:disabled {
    background: #6c757d;
    cursor: not-allowed;
    transform: none;
    box-shadow: none;
}

.btn-success {
    background: var(--success-gradient);
    color: white;
    box-shadow: 0 4px 15px rgba(67, 233, 123, 0.3);
}
.btn-success:hover {
    box-shadow: 0 8px 25px rgba(67, 233, 123, 0.4);
    transform: translateY(-2px) scale(1.02);
}

.btn-secondary {
    background: linear-gradient(135deg, #6c757d, #5a6268);
    color: white;
    box-shadow: 0 4px 15px rgba(108, 117, 125, 0.3);
}
.btn-secondary:hover {
    box-shadow: 0 8px 25px rgba(108, 117, 125, 0.4);
    transform: translateY(-2px) scale(1.02);
}

.btn-outline-primary {
    background: rgba(102, 126, 234, 0.1);
    color: #667eea;
    border: 1px solid rgba(102, 126, 234, 0.3);
}
.btn-outline-primary:hover {
    background: var(--primary-gradient);
    color: white;
    border-color: transparent;
    transform: translateY(-2px);
}

.btn-sm {
    padding: 8px 16px;
    font-size: 0.8rem;
    border-radius: var(--border-radius-sm);
    white-space: nowrap;
    min-width: auto;
}

.btn-lg {
    padding: 16px 32px;
    font-size: 1rem;
}

.selected-indicator {
    position: absolute;
    top: var(--spacing-sm);
    left: var(--spacing-sm);
    background: var(--success-gradient);
    color: white;
    padding: var(--spacing-xs) var(--spacing-sm);
    border-radius: var(--border-radius-md);
    font-size: 0.7rem;
    font-weight: 700;
    z-index: 10;
    box-shadow: 0 4px 15px rgba(40, 167, 69, 0.4);
    animation: selectedPulse 2s ease-in-out infinite;
}

@keyframes selectedPulse {
    0%, 100% {
        transform: scale(1);
        box-shadow: 0 4px 15px rgba(40, 167, 69, 0.4);
    }
    50% {
        transform: scale(1.05);
        box-shadow: 0 6px 20px rgba(40, 167, 69, 0.6);
    }
}

.template-preview-iframe {
    width: 1280px;
    height: 720px;
    border: none;
    pointer-events: none;
    position: absolute;
    left: 50%;
    top: 50%;
    transform: translate(-50%, -50%) scale(0.32);
    transform-origin: center center;
    border-radius: 4px;
}

.preview-overlay {
    position: absolute;
    top: 0;
    left: 0;
    width: 100%;
    height: 100%;
    background: rgba(0, 0, 0, 0);
    display: flex;
    align-items: center;
    justify-content: center;
    cursor: pointer;
    transition: background-color 0.3s ease;
}

.preview-overlay:hover {
    background: rgba(0, 0, 0, 0.1);
}

.preview-overlay-text {
    background: rgba(0, 0, 0, 0.7);
    color: white;
    padding: 8px 12px;
    border-radius: 4px;
    font-size: 12px;
    opacity: 0;
    transition: opacity 0.3s ease;
}

.preview-overlay:hover .preview-overlay-text {
    opacity: 1;
}

/* Loading state for iframes */
.template-preview::before {
    content: '';
    position: absolute;
    top: 50%;
    left: 50%;
    transform: translate(-50%, -50%);
    width: 24px;
    height: 24px;
    border: 3px solid rgba(67, 233, 123, 0.2);
    border-top: 3px solid var(--success-gradient);
    border-radius: 50%;
    animation: spin 1s linear infinite;
    z-index: 2;
    display: block;
}

.template-preview.loaded::before {
    display: none;
}

.template-preview.error::before {
    display: none;
}

.template-preview.error::after {
    content: '📄 预览加载失败\A点击重试';
    white-space: pre;
    position: absolute;
    top: 50%;
    left: 50%;
    transform: translate(-50%, -50%);
    color: #666;
    font-size: 14px;
    text-align: center;
    z-index: 2;
    cursor: pointer;
    padding: 12px;
    background: rgba(255, 255, 255, 0.9);
    border-radius: 8px;
    border: 1px solid #ddd;
}

.template-preview.error::after:hover {
    background: rgba(255, 255, 255, 1);
    color: #333;
}

/* Search and Filter Styles */
#searchInput:focus {
    outline: none;
    border-color: rgba(67, 233, 123, 0.5);
    box-shadow: 0 0 0 3px rgba(67, 233, 123, 0.1);
}

#tagFilter:focus {
    outline: none;
    border-color: rgba(67, 233, 123, 0.5);
    box-shadow: 0 0 0 3px rgba(67, 233, 123, 0.1);
}

.filter-tag {
    display: inline-flex;
    align-items: center;
    gap: var(--spacing-xs);
    background: rgba(67, 233, 123, 0.1);
    color: var(--success-gradient);
    padding: var(--spacing-xs) var(--spacing-sm);
    border-radius: var(--border-radius-sm);
    font-size: 0.8rem;
    font-weight: 500;
    border: 1px solid rgba(67, 233, 123, 0.2);
}

.filter-tag button {
    background: none;
    border: none;
    color: inherit;
    cursor: pointer;
    font-size: 0.9rem;
    padding: 0;
    margin-left: var(--spacing-xs);
}

.filter-tag button:hover {
    opacity: 0.7;
}

/* Pagination Styles */
.page-btn {
    min-width: 36px;
    height: 36px;
    padding: var(--spacing-xs) var(--spacing-sm);
    border: 1px solid var(--glass-border);
    background: rgba(255, 255, 255, 0.1);
    color: var(--text-primary);
    border-radius: var(--border-radius-sm);
    cursor: pointer;
    font-size: 0.9rem;
    font-weight: 500;
    transition: all 0.3s ease;
    display: flex;
    align-items: center;
    justify-content: center;
}

.page-btn:hover:not(:disabled) {
    background: rgba(67, 233, 123, 0.1);
    border-color: rgba(67, 233, 123, 0.3);
    transform: translateY(-1px);
}

.page-btn.active {
    background: var(--success-gradient);
    color: white;
    border-color: transparent;
    box-shadow: 0 2px 8px rgba(67, 233, 123, 0.3);
}

.page-btn:disabled {
    opacity: 0.5;
    cursor: not-allowed;
    transform: none;
}

.page-ellipsis {
    color: var(--text-muted);
    padding: var(--spacing-xs) var(--spacing-sm);
    font-size: 0.9rem;
}

/* 响应式设计 */
@media (max-width: 1200px) {
    #templatesGrid {
        grid-template-columns: repeat(auto-fill, minmax(350px, 1fr)) !important;
        gap: var(--spacing-lg) !important;
    }
}

@media (max-width: 768px) {
    .template-selection-hero {
        padding: var(--spacing-lg) var(--spacing-md);
    }

    .template-selection-hero h1 {
        font-size: 2.5rem;
    }

    .template-selection-hero p {
        font-size: 1.1rem;
    }

    /* Search and Filter Controls - Mobile */
    .search-filter-controls > div:first-child {
        flex-direction: column !important;
        align-items: stretch !important;
        gap: var(--spacing-md) !important;
    }

    .search-filter-controls > div:first-child > div {
        min-width: auto !important;
    }

    .search-filter-controls > div:first-child > div:nth-child(2) {
        flex-direction: column !important;
        align-items: stretch !important;
        gap: var(--spacing-sm) !important;
    }

    .search-filter-controls > div:first-child > div:nth-child(2) select {
        min-width: auto !important;
    }

    #templatesGrid {
        grid-template-columns: 1fr !important;
        gap: var(--spacing-md) !important;
    }

    .template-preview {
        height: 200px !important;
    }

    .template-preview-iframe {
        transform: translate(-50%, -50%) scale(0.28) !important;
    }

    .template-actions {
        flex-direction: column !important;
        gap: 8px !important;
    }

    .btn-sm {
        width: 100% !important;
        text-align: center !important;
        justify-content: center !important;
    }

    .modal-content {
        width: 95% !important;
        margin: 20px;
    }

    .modal-body {
        padding: 20px;
    }

    /* Pagination - Mobile */
    #paginationContainer > div {
        padding: var(--spacing-md) !important;
    }

    #paginationContainer > div > div:first-child {
        flex-direction: column !important;
        gap: var(--spacing-md) !important;
    }

    #pageNumbers {
        order: 2;
    }

    #prevPageBtn, #nextPageBtn {
        order: 1;
        width: 100%;
        justify-content: center !important;
    }
}
</style>

<script>
// Global variables
let templates = [];
let selectedTemplateId = null;
let currentPage = 1;
let totalPages = 1;
let pageSize = 6;
let currentSearch = '';
let currentTag = '';
let allTags = [];

// Extract project ID from URL path: /projects/{project_id}/template-selection
let pathParts = window.location.pathname.split('/');
let projectId = pathParts[2]; // Should be the project ID (pathParts: ['', 'projects', 'project_id', 'template-selection'])

console.log('URL pathname:', window.location.pathname);
console.log('Path parts:', pathParts);
console.log('Extracted project ID:', projectId);

// Initialize page
document.addEventListener('DOMContentLoaded', function() {
    console.log('Current URL:', window.location.pathname);
    console.log('Path parts:', pathParts);
    console.log('Project ID:', projectId);

    // Validate project ID format
    if (!projectId || projectId === 'undefined' || projectId === 'projects') {
        alert('错误：无法获取项目ID。当前路径：' + window.location.pathname + '\n\n请确保URL格式正确：/projects/{项目ID}/template-selection');
        return;
    }

    // Additional validation for common invalid project IDs
    if (['template-selection', 'todo', 'edit', 'preview', 'fullscreen'].includes(projectId)) {
        alert('错误：项目ID格式无效 (' + projectId + ')。\n\n请从项目列表页面正确访问模板选择页面。');
        window.location.href = '/projects';
        return;
    }

    loadTemplates(1);
    setupEventListeners();
    setupSearchListeners();
});

function setupEventListeners() {
    console.log('Setting up event listeners...');

    // Modal controls
    const closeBtn = document.getElementById('closePreviewModal');
    if (closeBtn) {
        closeBtn.addEventListener('click', () => closePreviewModal());
        console.log('Close preview modal listener added');
    }

    // Action buttons
    const startBtn = document.getElementById('startGenerationBtn');
    const skipBtn = document.getElementById('skipSelectionBtn');

    if (startBtn) {
        startBtn.addEventListener('click', function(e) {
            console.log('Start generation button clicked');
            e.preventDefault();
            startPPTGeneration();
        });
        console.log('Start generation button listener added');
    } else {
        console.error('Start generation button not found');
    }

    if (skipBtn) {
        skipBtn.addEventListener('click', function(e) {
            console.log('Skip selection button clicked');
            e.preventDefault();
            useDefaultTemplate();
        });
        console.log('Skip selection button listener added');
    } else {
        console.error('Skip selection button not found');
    }

    // Close modal when clicking outside
    window.addEventListener('click', function(event) {
        if (event.target.classList.contains('modal')) {
            event.target.style.display = 'none';
        }
    });

    console.log('Event listeners setup complete');
}

function setupSearchListeners() {
    const searchInput = document.getElementById('searchInput');

    // Add input event listener for real-time search button visibility
    searchInput.addEventListener('input', function() {
        updateClearSearchButton();
    });

    // Add keyup event listener for Enter key
    searchInput.addEventListener('keyup', function(event) {
        if (event.key === 'Enter') {
            performSearch();
        }
    });

    console.log('Search listeners setup complete');
}

async function loadTemplates(page = 1) {
    showLoading(true);
    try {
        // Build query parameters
        const params = new URLSearchParams({
            active_only: 'true',
            page: page.toString(),
            page_size: pageSize.toString()
        });

        if (currentSearch) {
            params.append('search', currentSearch);
        }

        if (currentTag) {
            params.append('tags', currentTag);
        }

        const response = await fetch(`/api/global-master-templates/?${params}`);

        if (!response.ok) {
            throw new Error('Failed to load templates');
        }

        const data = await response.json();
        console.log('API response:', data);

        // 确保我们获取的是模板数组和分页信息
        if (data && Array.isArray(data.templates) && data.pagination) {
            templates = data.templates;
            currentPage = data.pagination.current_page;
            totalPages = data.pagination.total_pages;

            // Update pagination info
            updatePaginationInfo(data.pagination);
        } else if (Array.isArray(data)) {
            // 如果直接返回数组（向后兼容）
            templates = data;
            currentPage = 1;
            totalPages = 1;
        } else {
            console.error('Unexpected API response format:', data);
            throw new Error('Invalid response format from templates API');
        }

        console.log('Loaded templates:', templates);
        renderTemplates(templates);

        // Load all tags for filter dropdown
        if (page === 1) {
            await loadAllTags();
        }

    } catch (error) {
        console.error('Error loading templates:', error);
        alert('加载模板失败: ' + error.message);
    } finally {
        showLoading(false);
    }
}

function renderTemplates(templatesToRender) {
    const grid = document.getElementById('templatesGrid');

    // 确保 templatesToRender 是一个数组
    if (!Array.isArray(templatesToRender)) {
        console.error('renderTemplates: templatesToRender is not an array:', templatesToRender);
        grid.innerHTML = `
            <div style="grid-column: 1 / -1; text-align: center; padding: var(--spacing-2xl); background: var(--glass-bg); backdrop-filter: blur(15px); border: 1px solid var(--glass-border); border-radius: var(--border-radius-lg); box-shadow: var(--glass-shadow);">
                <div style="font-size: 4rem; margin-bottom: var(--spacing-lg); opacity: 0.6;">⚠️</div>
                <h3 style="color: var(--text-primary); font-size: 1.5rem; margin-bottom: var(--spacing-md); font-weight: 600;">数据格式错误</h3>
                <p style="color: var(--text-secondary); font-size: 1rem; margin-bottom: var(--spacing-lg);">模板数据格式不正确，请刷新页面重试</p>
                <button class="btn btn-primary" onclick="window.location.reload()" style="margin-top: var(--spacing-md);">
                    🔄 刷新页面
                </button>
            </div>
        `;
        return;
    }

    if (templatesToRender.length === 0) {
        grid.innerHTML = `
            <div style="grid-column: 1 / -1; text-align: center; padding: var(--spacing-2xl); background: var(--glass-bg); backdrop-filter: blur(15px); border: 1px solid var(--glass-border); border-radius: var(--border-radius-lg); box-shadow: var(--glass-shadow);">
                <div style="font-size: 4rem; margin-bottom: var(--spacing-lg); opacity: 0.6;">🎨</div>
                <h3 style="color: var(--text-primary); font-size: 1.5rem; margin-bottom: var(--spacing-md); font-weight: 600;">暂无可用模板</h3>
                <p style="color: var(--text-secondary); font-size: 1rem; margin-bottom: var(--spacing-lg);">系统中还没有可用的PPT模板</p>
                <button class="btn btn-primary" onclick="window.location.reload()" style="margin-top: var(--spacing-md);">
                    🔄 刷新页面
                </button>
            </div>
        `;
        return;
    }
    
    grid.innerHTML = templatesToRender.map(template => `
        <div class="template-card" data-template-id="${template.id}" onclick="selectTemplate(${template.id})">
            <div class="template-preview" id="preview-${template.id}">
                <iframe
                    class="template-preview-iframe"
                    id="iframe-${template.id}"
                    onload="adjustIframeContent(${template.id})"
                ></iframe>
                <div class="preview-overlay" onclick="event.stopPropagation(); previewTemplate(${template.id})">
                    <div class="preview-overlay-text">🔍 点击放大预览</div>
                </div>
            </div>
            <div class="template-info">
                <div style="display: flex; justify-content: space-between; align-items: flex-start; margin-bottom: 8px;">
                    <h4 style="font-size: 16px; font-weight: 600; color: #2c3e50; margin: 0; line-height: 1.3;">${template.template_name}</h4>
                    ${template.is_default ? '<span class="default-badge">默认</span>' : ''}
                </div>
                <p style="color: #666; font-size: 14px; line-height: 1.4; margin: 0 0 12px 0; display: -webkit-box; -webkit-line-clamp: 2; -webkit-box-orient: vertical; overflow: hidden;">${template.description || '这是一个精美的PPT模板，适用于多种场景'}</p>
                <div style="margin-bottom: 12px; display: flex; flex-wrap: wrap; gap: 6px;">
                    ${(template.tags || []).map(tag => `<span class="tag">${tag}</span>`).join('')}
                </div>
                <div style="font-size: 12px; color: #999; margin-bottom: 0;">
                    使用次数: ${template.usage_count} | 创建者: ${template.created_by || '系统'}
                </div>
            </div>
            <div class="template-actions">
                <button class="btn btn-sm btn-outline-primary" onclick="event.stopPropagation(); previewTemplate(${template.id})">
                    👁️ 预览
                </button>
                <button class="btn btn-sm btn-success" onclick="event.stopPropagation(); console.log('Template card button clicked for template:', ${template.id}); selectAndStart(${template.id})">
                    ✅ 选择并开始
                </button>
            </div>
        </div>
    `).join('');

    // Load template content into iframes after rendering
    setTimeout(() => {
        console.log('Starting to load template previews for', templatesToRender.length, 'templates');
        templatesToRender.forEach(template => {
            console.log('Loading preview for template:', template.id, template.template_name);
            loadTemplatePreview(template.id);
        });
    }, 500);
}

function selectTemplate(templateId) {
    // Remove previous selection
    document.querySelectorAll('.template-card').forEach(card => {
        card.classList.remove('selected');
        const indicator = card.querySelector('.selected-indicator');
        if (indicator) indicator.remove();
    });

    // Add selection to clicked template
    const selectedCard = document.querySelector(`[data-template-id="${templateId}"]`);
    if (!selectedCard) {
        console.error('Template card not found for ID:', templateId);
        return;
    }

    selectedCard.classList.add('selected');

    // Add selected indicator
    const preview = selectedCard.querySelector('.template-preview');
    const indicator = document.createElement('span');
    indicator.className = 'selected-indicator';
    indicator.textContent = '已选择';
    preview.appendChild(indicator);

    selectedTemplateId = templateId;

    // Update selected template info
    const template = templates.find(t => t.id === templateId);
    if (template) {
        showSelectedTemplateInfo(template);
    }

    // Enable start button
    document.getElementById('startGenerationBtn').disabled = false;
}

function showSelectedTemplateInfo(template) {
    const infoDiv = document.getElementById('selectedTemplateInfo');
    const detailsDiv = document.getElementById('selectedTemplateDetails');

    const tags = template.tags && template.tags.length > 0 ? template.tags.join(', ') : '无';

    detailsDiv.innerHTML = `
        <strong>${template.template_name}</strong><br>
        <span style="color: #666;">${template.description || '暂无描述'}</span><br>
        <small style="color: #999;">标签: ${tags}</small>
    `;

    infoDiv.style.display = 'block';
}

async function previewTemplate(templateId) {
    try {
        const response = await fetch(`/api/global-master-templates/${templateId}/preview`);
        if (!response.ok) {
            throw new Error('Failed to load template preview');
        }
        
        const data = await response.json();
        showPreview(data.html_template, data.template_name);
    } catch (error) {
        console.error('Error loading template preview:', error);
        alert('加载预览失败: ' + error.message);
    }
}

function showPreview(htmlContent, templateName) {
    const modal = document.getElementById('previewModal');
    const frame = document.getElementById('previewFrame');
    const title = document.getElementById('previewTitle');
    
    title.textContent = `模板预览 - ${templateName}`;
    
    // Create blob URL for the HTML content
    const blob = new Blob([htmlContent], { type: 'text/html' });
    const url = URL.createObjectURL(blob);
    
    frame.src = url;
    modal.style.display = 'flex';
    
    // Clean up the blob URL after a delay
    setTimeout(() => {
        URL.revokeObjectURL(url);
    }, 1000);
}

function closePreviewModal() {
    document.getElementById('previewModal').style.display = 'none';
}

function selectAndStart(templateId) {
    console.log('selectAndStart called with templateId:', templateId);
    selectTemplate(templateId);
    setTimeout(() => {
        startPPTGeneration();
    }, 100); // 给选择操作一点时间完成
}

async function startPPTGeneration() {
    console.log('startPPTGeneration called');
    console.log('selectedTemplateId:', selectedTemplateId);
    console.log('projectId:', projectId);

    if (!selectedTemplateId) {
        alert('请先选择一个模板');
        return;
    }

    if (!projectId || projectId === 'undefined') {
        alert('错误：项目ID无效');
        return;
    }

    try {
        console.log('Sending request to select template...');

        // Select template for project
        const response = await fetch(`/api/projects/${projectId}/select-template`, {
            method: 'POST',
            headers: {
                'Content-Type': 'application/json',
            },
            body: JSON.stringify({
                project_id: projectId,
                selected_template_id: selectedTemplateId
            })
        });

        console.log('Response status:', response.status);
        console.log('Response ok:', response.ok);

        if (!response.ok) {
            let errorMessage = 'Failed to select template';
            try {
                const error = await response.json();
                console.log('Error response:', error);
                errorMessage = error.detail || error.message || errorMessage;
            } catch (e) {
                errorMessage = `HTTP ${response.status}: ${response.statusText}`;
            }
            throw new Error(errorMessage);
        }

        const result = await response.json();
        console.log('Template selection result:', result);

        // Redirect to TODO board to start PPT generation
        console.log('Redirecting to TODO board...');
        window.location.href = `/projects/${projectId}/todo`;

    } catch (error) {
        console.error('Error starting PPT generation:', error);
        alert('开始生成失败: ' + error.message);
    }
}

async function useDefaultTemplate() {
    console.log('useDefaultTemplate called');
    console.log('projectId:', projectId);

    if (!projectId || projectId === 'undefined') {
        alert('错误：项目ID无效');
        return;
    }

    try {
        console.log('Sending request to use default template...');

        // Use default template (null template_id)
        const response = await fetch(`/api/projects/${projectId}/select-template`, {
            method: 'POST',
            headers: {
                'Content-Type': 'application/json',
            },
            body: JSON.stringify({
                project_id: projectId,
                selected_template_id: null
            })
        });

        console.log('Response status:', response.status);
        console.log('Response ok:', response.ok);

        if (!response.ok) {
            let errorMessage = 'Failed to select default template';
            try {
                const error = await response.json();
                console.log('Error response:', error);
                errorMessage = error.detail || error.message || errorMessage;
            } catch (e) {
                errorMessage = `HTTP ${response.status}: ${response.statusText}`;
            }
            throw new Error(errorMessage);
        }

        const result = await response.json();
        console.log('Default template selection result:', result);

        // Redirect to TODO board to start PPT generation
        console.log('Redirecting to TODO board...');
        window.location.href = `/projects/${projectId}/todo`;

    } catch (error) {
        console.error('Error using default template:', error);
        alert('使用默认模板失败: ' + error.message);
    }
}

function showLoading(show) {
    document.getElementById('loadingIndicator').style.display = show ? 'block' : 'none';
    document.getElementById('templatesGrid').style.display = show ? 'none' : 'grid';
}

async function loadTemplatePreview(templateId) {
    try {
        console.log('Loading preview for template', templateId);
        const response = await fetch('{{ root_path }}/api/global-master-templates/' + templateId);
        if (!response.ok) {
            console.warn('Failed to load template', templateId, 'for preview');
            showPreviewFallback(templateId);
            return;
        }

        const template = await response.json();
        const iframe = document.getElementById('iframe-' + templateId);

        console.log('Template', templateId, 'loaded:', template.template_name);

        if (iframe && template.html_template && template.html_template.trim()) {
            console.log('Setting up iframe for template', templateId);

            // 使用实际的模板HTML内容，但添加一些示例数据
            let previewHtml = template.html_template;

            // 替换模板变量为示例内容
            previewHtml = previewHtml.replace(/\{\{\s*title\s*\}\}/g, template.template_name);
            previewHtml = previewHtml.replace(/\{\{\s*content\s*\}\}/g, '这是模板预览内容');
            previewHtml = previewHtml.replace(/\{\{\s*slide_number\s*\}\}/g, '1');
            previewHtml = previewHtml.replace(/\{\{\s*total_slides\s*\}\}/g, '1');

            // 确保HTML有基本结构
            if (!previewHtml.includes('<!DOCTYPE') && !previewHtml.includes('<html')) {
                previewHtml = `<!DOCTYPE html>
<html>
<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <style>
        body { width: 1280px; height: 720px; margin: 0; padding: 0; overflow: hidden; }
    </style>
</head>
<body>
    ${previewHtml}
</body>
</html>`;
            }

            // Create a blob URL for the HTML content
            const blob = new Blob([previewHtml], { type: 'text/html' });
            const url = URL.createObjectURL(blob);

            // Set up load handlers
            iframe.onload = function() {
                console.log('Iframe loaded successfully for template', templateId);
                // Remove loading state
                const previewContainer = document.getElementById('preview-' + templateId);
                if (previewContainer) {
                    previewContainer.classList.add('loaded');
                }
                setTimeout(function() {
                    URL.revokeObjectURL(url);
                }, 2000);
            };

            iframe.onerror = function() {
                console.warn('Iframe failed to load for template', templateId);
                // Remove loading state and show error
                const previewContainer = document.getElementById('preview-' + templateId);
                if (previewContainer) {
                    previewContainer.classList.add('error');
                    previewContainer.classList.remove('loaded');
                }
                showPreviewFallback(templateId);
                URL.revokeObjectURL(url);
            };

            // Set the src to trigger loading
            iframe.src = url;

        } else {
            console.warn('No HTML template content for template', templateId);
            // Remove loading state and show fallback
            const previewContainer = document.getElementById('preview-' + templateId);
            if (previewContainer) {
                previewContainer.classList.add('error');
                previewContainer.classList.remove('loaded');
            }
            showPreviewFallback(templateId);
        }
    } catch (error) {
        console.error('Error loading preview for template', templateId, ':', error);
        // Remove loading state and show fallback
        const previewContainer = document.getElementById('preview-' + templateId);
        if (previewContainer) {
            previewContainer.classList.add('error');
            previewContainer.classList.remove('loaded');
        }
        showPreviewFallback(templateId);
    }
}

function showPreviewFallback(templateId) {
    const iframe = document.getElementById('iframe-' + templateId);
    const previewContainer = document.getElementById('preview-' + templateId);

    if (!iframe) return;

    // Remove loading state
    if (previewContainer) {
        previewContainer.classList.add('loaded');
        previewContainer.classList.remove('error');
    }

    const fallbackHtml = `
        <!DOCTYPE html>
        <html>
        <head>
            <meta charset="UTF-8">
            <style>
                body {
                    margin: 0;
                    padding: 0;
                    display: flex;
                    align-items: center;
                    justify-content: center;
                    width: 1280px;
                    height: 720px;
                    font-family: -apple-system, BlinkMacSystemFont, 'Segoe UI', Roboto, sans-serif;
                    background: linear-gradient(135deg, #f8f9fa 0%, #e9ecef 100%);
                    color: #666;
                    overflow: hidden;
                }
                .fallback-content {
                    text-align: center;
                    padding: 40px;
                    border-radius: 12px;
                    background: rgba(255, 255, 255, 0.9);
                    box-shadow: 0 4px 20px rgba(0, 0, 0, 0.1);
                }
                .fallback-icon {
                    font-size: 48px;
                    margin-bottom: 16px;
                    opacity: 0.8;
                }
                .fallback-title {
                    font-size: 24px;
                    margin-bottom: 8px;
                    font-weight: 600;
                }
                .fallback-subtitle {
                    font-size: 16px;
                    opacity: 0.7;
                }
            </style>
        </head>
        <body>
            <div class="fallback-content">
                <div class="fallback-icon">📄</div>
                <div class="fallback-title">模板预览</div>
                <div class="fallback-subtitle">暂无预览</div>
            </div>
        </body>
        </html>
    `;

    const blob = new Blob([fallbackHtml], { type: 'text/html' });
    const url = URL.createObjectURL(blob);

    iframe.onload = function() {
        setTimeout(() => {
            URL.revokeObjectURL(url);
        }, 1000);
    };

    iframe.src = url;
}

function adjustIframeContent(templateId) {
    try {
        console.log('Iframe loaded for template:', templateId);
        // Remove loading state when iframe loads
        const previewContainer = document.getElementById('preview-' + templateId);
        if (previewContainer) {
            previewContainer.classList.add('loaded');
            previewContainer.classList.remove('error');
        }
        // Additional adjustments can be made here if needed
    } catch (error) {
        console.error('Error adjusting iframe content:', error);
        const previewContainer = document.getElementById('preview-' + templateId);
        if (previewContainer) {
            previewContainer.classList.add('error');
            previewContainer.classList.remove('loaded');
        }
        showPreviewFallback(templateId);
    }
}

// Search and Filter Functions
async function performSearch() {
    const searchInput = document.getElementById('searchInput');
    const newSearch = searchInput.value.trim();

    if (newSearch !== currentSearch) {
        currentSearch = newSearch;
        currentPage = 1; // Reset to first page
        await loadTemplates(1);
        updateActiveFilters();
        updateClearSearchButton();
    }
}

function clearSearch() {
    const searchInput = document.getElementById('searchInput');
    searchInput.value = '';
    if (currentSearch !== '') {
        currentSearch = '';
        currentPage = 1;
        loadTemplates(1);
        updateActiveFilters();
        updateClearSearchButton();
    }
}

async function filterByTag() {
    const tagFilter = document.getElementById('tagFilter');
    const newTag = tagFilter.value;

    if (newTag !== currentTag) {
        currentTag = newTag;
        currentPage = 1; // Reset to first page
        await loadTemplates(1);
        updateActiveFilters();
    }
}

function clearAllFilters() {
    const searchInput = document.getElementById('searchInput');
    const tagFilter = document.getElementById('tagFilter');

    searchInput.value = '';
    tagFilter.value = '';
    currentSearch = '';
    currentTag = '';
    currentPage = 1;

    loadTemplates(1);
    updateActiveFilters();
    updateClearSearchButton();
}

function updateActiveFilters() {
    const activeFilters = document.getElementById('activeFilters');
    const filterTags = document.getElementById('filterTags');

    const filters = [];

    if (currentSearch) {
        filters.push({
            type: 'search',
            label: `搜索: "${currentSearch}"`,
            value: currentSearch
        });
    }

    if (currentTag) {
        filters.push({
            type: 'tag',
            label: `分类: ${currentTag}`,
            value: currentTag
        });
    }

    if (filters.length > 0) {
        filterTags.innerHTML = filters.map(filter => `
            <span class="filter-tag">
                ${filter.label}
                <button onclick="removeFilter('${filter.type}')">✕</button>
            </span>
        `).join('');
        activeFilters.style.display = 'block';
    } else {
        activeFilters.style.display = 'none';
    }
}

function removeFilter(type) {
    if (type === 'search') {
        document.getElementById('searchInput').value = '';
        currentSearch = '';
        updateClearSearchButton();
    } else if (type === 'tag') {
        document.getElementById('tagFilter').value = '';
        currentTag = '';
    }

    currentPage = 1;
    loadTemplates(1);
    updateActiveFilters();
}

function updateClearSearchButton() {
    const clearBtn = document.getElementById('clearSearchBtn');
    const searchInput = document.getElementById('searchInput');

    if (searchInput.value.trim()) {
        clearBtn.style.display = 'block';
    } else {
        clearBtn.style.display = 'none';
    }
}

// Pagination Functions
async function changePage(page) {
    if (page < 1 || page > totalPages || page === currentPage) {
        return;
    }

    await loadTemplates(page);
}

function updatePaginationInfo(pagination) {
    const paginationContainer = document.getElementById('paginationContainer');
    const pageNumbers = document.getElementById('pageNumbers');
    const pageInfo = document.getElementById('pageInfo');
    const prevBtn = document.getElementById('prevPageBtn');
    const nextBtn = document.getElementById('nextPageBtn');

    // Show pagination if there are multiple pages
    if (pagination.total_pages > 1) {
        paginationContainer.style.display = 'block';

        // Update page info
        pageInfo.textContent = `第 ${pagination.current_page} 页，共 ${pagination.total_pages} 页 (总计 ${pagination.total_count} 个模板)`;

        // Update navigation buttons
        prevBtn.disabled = pagination.current_page <= 1;
        nextBtn.disabled = pagination.current_page >= pagination.total_pages;

        // Generate page numbers
        generatePageNumbers(pagination.current_page, pagination.total_pages);
    } else {
        paginationContainer.style.display = 'none';
    }
}

function generatePageNumbers(current, total) {
    const pageNumbers = document.getElementById('pageNumbers');
    const maxVisible = 7; // Maximum number of page buttons to show

    let pages = [];

    if (total <= maxVisible) {
        // Show all pages if total is small
        for (let i = 1; i <= total; i++) {
            pages.push(i);
        }
    } else {
        // Smart pagination with ellipsis
        if (current <= 4) {
            // Show first pages
            pages = [1, 2, 3, 4, 5, '...', total];
        } else if (current >= total - 3) {
            // Show last pages
            pages = [1, '...', total - 4, total - 3, total - 2, total - 1, total];
        } else {
            // Show middle pages
            pages = [1, '...', current - 1, current, current + 1, '...', total];
        }
    }

    pageNumbers.innerHTML = pages.map(page => {
        if (page === '...') {
            return '<span class="page-ellipsis">...</span>';
        } else {
            const isActive = page === current;
            return `
                <button
                    class="page-btn ${isActive ? 'active' : ''}"
                    onclick="changePage(${page})"
                    ${isActive ? 'disabled' : ''}
                >
                    ${page}
                </button>
            `;
        }
    }).join('');
}

// Load all available tags for filter dropdown
async function loadAllTags() {
    try {
        // Get all templates to extract unique tags
        const response = await fetch('{{ root_path }}/api/global-master-templates/?active_only=true&page_size=1000');
        if (!response.ok) return;

        const data = await response.json();
        const templates = data.templates || data;

        // Extract all unique tags
        const tagSet = new Set();
        templates.forEach(template => {
            if (template.tags && Array.isArray(template.tags)) {
                template.tags.forEach(tag => tagSet.add(tag));
            }
        });

        allTags = Array.from(tagSet).sort();

        // Populate tag filter dropdown
        const tagFilter = document.getElementById('tagFilter');
        tagFilter.innerHTML = '<option value="">全部分类</option>' +
            allTags.map(tag => `<option value="${tag}">${tag}</option>`).join('');

    } catch (error) {
        console.error('Error loading tags:', error);
    }
}


</script>
{% endblock %}
